using System.Collections.Generic;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Media;

namespace GameFramework.Managers
{
    /// <summary>
    /// The sound manager.
    /// </summary>
    public static class SoundManager
    {
        /// <summary>
        /// Initializes static members of the <see cref="SoundManager"/> class.
        /// </summary>
        static SoundManager()
        {
            SoundEffects = new Dictionary<string, SoundEffect>();
            Songs = new Dictionary<string, Song>();
        }

        /// <summary>
        /// Gets or sets SoundEffects.
        /// </summary>
        public static Dictionary<string, SoundEffect> SoundEffects { get; set; }

        /// <summary>
        /// Gets or sets Songs.
        /// </summary>
        public static Dictionary<string, Song> Songs { get; set; }

        /// <summary>
        /// Load a sound effect.
        /// </summary>
        /// <param name="assetName">The asset name.</param>
        /// <param name="soundEffectName">The sound effect name.</param>
        public static void LoadSoundEffect(string assetName, string soundEffectName)
        {
            SoundEffects[soundEffectName] = Global.Game.Content.Load<SoundEffect>(assetName);
        }

        /// <summary>
        /// Load a sound. The asset name will be "sounds/" followed by the sound name.
        /// </summary>
        /// <param name="soundName">The texture name.</param>
        public static void LoadSoundEffect(string soundName)
        {
            SoundEffects[soundName] = Global.Game.Content.Load<SoundEffect>("sounds/" + soundName);
        }

        /// <summary>
        /// Load a song.
        /// </summary>
        /// <param name="assetName">The asset name.</param>
        /// <param name="songName">The song name.</param>
        public static void LoadSong(string assetName, string songName)
        {
            Songs[songName] = Global.Game.Content.Load<Song>(assetName);
        }

        /// <summary>
        /// Load a song. The asset name will be "songs/" followed by the song name.
        /// </summary>
        /// <param name="songName">The texture name.</param>
        public static void LoadSong(string songName)
        {
            Songs[songName] = Global.Game.Content.Load<Song>("songs/" + songName);
        }

        /// <summary>
        /// Play a sound effect. 
        /// </summary>
        /// <param name="soundEffectName">The name of the sound effect.</param>
        public static void PlaySound(string soundEffectName)
        {
            SoundEffect soundEffect;

            if (SoundEffects.TryGetValue(soundEffectName, out soundEffect))
            {
                soundEffect.Play();
            }
        }

        /// <summary>
        /// Play a sound effect with specific values for volume, pitch and pan.
        /// </summary>
        /// <param name="soundEffectName">The name of the sound effect.</param>
        /// <param name="volume">The volume.</param>
        /// <param name="pitch">The pitch.</param>
        /// <param name="pan">The pan.</param>
        public static void PlaySound(string soundEffectName, float volume, float pitch, float pan)
        {
            SoundEffect soundEffect;

            if (SoundEffects.TryGetValue(soundEffectName, out soundEffect))
            {
                soundEffect.Play(volume, pitch, pan);
            }
        }

        /// <summary>
        /// Play a song.
        /// </summary>
        /// <param name="songName">The song name.</param>
        public static void PlayMusic(string songName)
        {
            PlayMusic(songName, 1.0f, true);
        }

        /// <summary>
        /// Play a song with a specific volume and/or in repeating mode.
        /// </summary>
        /// <param name="songName">The song name.</param>
        /// <param name="volume">The song volume.</param>
        /// <param name="isRepeating">True if you want to repeat the song.</param>
        public static void PlayMusic(string songName, float volume, bool isRepeating)
        {
            if (!MediaPlayer.GameHasControl)
            {
                return;
            }

            Song song;

            if (Songs.TryGetValue(songName, out song))
            {
                MediaPlayer.Volume = volume;
                MediaPlayer.IsRepeating = isRepeating;
                MediaPlayer.Play(song);
            }
        }

        /// <summary>
        /// Put the music in pause.
        /// </summary>
        public static void PauseMusic()
        {
            if (MediaPlayer.GameHasControl)
            {
                MediaPlayer.Pause();
            }
        }

        /// <summary>
        /// Resume the music.
        /// </summary>
        public static void ResumeMusic()
        {
            if (MediaPlayer.GameHasControl)
            {
                MediaPlayer.Resume();
            }
        }

        /// <summary>
        /// Stop the music.
        /// </summary>
        public static void StopMusic()
        {
            if (MediaPlayer.GameHasControl)
            {
                MediaPlayer.Stop();
            }
        }
    }
}
